﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Drawing;
using System.Collections;
using System.ComponentModel;
using System.Windows.Forms;
using System.Data;
using System.Drawing.Imaging;
using System.Runtime.InteropServices;

namespace ColorPicker
{
    public class PreviewControl : Control
    {
        public const int SubImgSize = 7; // 像素多少
        public const int ScaleFact = 32; // 窗口倍数
        Bitmap img;
        public PreviewControl(Bitmap img)
        {
            this.img = img;

            this.SetStyle(ControlStyles.AllPaintingInWmPaint, true); // 双缓冲
            this.SetStyle(ControlStyles.OptimizedDoubleBuffer, true);
        }


        protected override void OnPaint(PaintEventArgs e)
        {
            base.OnPaint(e);

            Point mp = Cursor.Position;

            // draw image
            //e.Graphics.SmoothingMode = System.Drawing.Drawing2D.SmoothingMode.None;
            //e.Graphics.DrawImage(img,
            //    this.Bounds,
            //    new Rectangle(mp.X - PreviewForm.subImgSize / 2, mp.Y - PreviewForm.subImgSize / 2,  PreviewForm.subImgSize, PreviewForm.subImgSize),
            //    GraphicsUnit.Pixel);
            DrawBitmap(e.Graphics);

            // draw border
            int borderSize = 4;
            var borderRect = this.Bounds;
            borderRect.X += borderSize / 2;
            borderRect.Y += borderSize / 2;
            borderRect.Width -= borderSize;
            borderRect.Height -= borderSize;
            var borderPen = new Pen(new SolidBrush(Color.Red));
            borderPen.Width = borderSize;
            e.Graphics.DrawRectangle(borderPen, borderRect);
        }

        void DrawBitmap(Graphics g)
        {
            Point mp = Cursor.Position;
            var srcRect = new Rectangle(mp.X - SubImgSize / 2, mp.Y - SubImgSize / 2, SubImgSize, SubImgSize);
            var destRect = this.Bounds;
            var imgRect = new Rectangle(0, 0, img.Width, img.Height);
            for (int x = 0; x < SubImgSize; x++)
            {
                for (int y = 0; y < SubImgSize; y++)
                {
                    var pos = new Point(srcRect.X + x, srcRect.Y + y);
                    if (imgRect.Contains(pos))
                    {
                        var c = img.GetPixel(pos.X, pos.Y);
                        g.FillRectangle(new SolidBrush(c), new Rectangle(x * ScaleFact, y * ScaleFact, ScaleFact, ScaleFact));
                    }
                }
            }

            // draw middle line
            var p = new Point((SubImgSize / 2 + 0) * ScaleFact, (SubImgSize / 2 + 0) * ScaleFact);
            var w = this.Bounds.Width;
            g.DrawRectangle(new Pen(new SolidBrush(Color.Red)), new Rectangle(0, p.Y, w, ScaleFact));
            g.DrawRectangle(new Pen(new SolidBrush(Color.Red)), new Rectangle(p.X, 0, ScaleFact, w));
        }

    }

    public class PreviewForm : Form
    {
        Bitmap img;
        public PreviewForm(Bitmap img)
        {
            this.img = img;

            this.TopMost = true;
            this.ShowInTaskbar = false;
            this.FormBorderStyle = FormBorderStyle.None;
            this.Size = new Size(PreviewControl.ScaleFact * PreviewControl.SubImgSize, PreviewControl.ScaleFact * PreviewControl.SubImgSize);
            this.SetStyle(ControlStyles.AllPaintingInWmPaint, true); // 双缓冲
            this.SetStyle(ControlStyles.OptimizedDoubleBuffer, true);
            this.KeyDown += (sender, e) =>
            {
                if (e.KeyCode == Keys.Escape)
                    Application.Exit();
            };
            this.MouseClick += (s, e) => Application.Exit();


            var pic = new PreviewControl(img);
            pic.Parent = this;
            pic.Size = this.Size;

            var timer = new Timer();
            timer.Interval = 10;
            timer.Tick += (s, e) =>
            {
                int offsetBase = 100;
                Point mp = Cursor.Position;
                var rect = Screen.FromControl(this).Bounds;
                var offsetX = mp.X < rect.Width / 2 ? +offsetBase : -(offsetBase + pic.Width);
                var offsetY = mp.Y < rect.Height / 2 ? +offsetBase : -(offsetBase + pic.Height);

                //var pos = new Point(mp.X + this.Width + 10, mp.Y + this.Height + 10);
                //// clamp in window
                //pos.X = Math.Min(this.Width - rect.Width, pos.X);
                //pos.Y = Math.Min(this.Height - rect.Height, pos.Y);
                this.Location = new Point(mp.X + offsetX, mp.Y + offsetY);
                pic.Invalidate();
            };
            timer.Start();
            this.Show();
        }
    }

    public class FormColorPicker : Form
    {
        public FormColorPicker()
        {
            //初始化窗体中的各个组件 
            InitializeComponent();
        }

        bool success = false;
        Bitmap img;

        private void InitializeComponent()
        {
            // 捕获图片
            //获得当前屏幕的大小 
            this.ShowIcon = false;
            this.Text = "-- screen shot --";
            Rectangle screenRect = Screen.GetWorkingArea(this);
            img = CaptureScreen(screenRect);

            // 调整样式
            //this.TopMost = true; // 置顶
            this.SetStyle(ControlStyles.AllPaintingInWmPaint, true); // 双缓冲
            this.SetStyle(ControlStyles.OptimizedDoubleBuffer, true);
            this.FormBorderStyle = FormBorderStyle.None;
            this.WindowState = FormWindowState.Maximized;
            this.BackgroundImage = img;

            // 截图预览窗口
            if (success)
            {
               new PreviewForm(img);
            }

            // 监听退出
            this.KeyDown += (sender, e) =>
            {
                if (success == false)
                {
                    Application.Exit();
                }
                if (e.KeyCode == Keys.Escape)
                    Application.Exit();
            };
            this.MouseClick += (s, e) =>
            {
                Point mp = Cursor.Position;
                var imgRect = new Rectangle(0, 0, img.Width, img.Height);
                Color c = (imgRect.Contains(mp)) ? img.GetPixel(mp.X, mp.Y) : Color.Black;
                //using (var stdout = Console.OpenStandardOutput())
                //{
                //    using (var sw = new System.IO.StreamWriter(stdout))
                //    {
                //        sw.WriteLine($"{c.R},{c.G},{c.B}");
                //    }
                //}
                Console.WriteLine($"{c.R},{c.G},{c.B}");
                Application.Exit();
            };
        }

        // 截屏
        private Bitmap CaptureScreen(Rectangle captureRectangle)
        {
            Bitmap captureBitmap = new Bitmap(captureRectangle.Width, captureRectangle.Height, PixelFormat.Format32bppArgb);
            Graphics captureGraphics = Graphics.FromImage(captureBitmap);
            try
            {
                captureGraphics.CopyFromScreen(captureRectangle.Left, captureRectangle.Top, 0, 0, captureRectangle.Size);
                success = true;
            }
            catch (Exception ex)
            {
                var font = new Font(FontFamily.GenericMonospace, 20);
                captureGraphics.DrawString("按下ESC退出\n error: \n" + ex.ToString(), font, new SolidBrush(Color.Red), new PointF());
            }
            return captureBitmap;
        }


        static void Main(string[] args)
        {
            Application.Run(new FormColorPicker());
        }
    }
}
